package com.whoimi.common.jdbc;

import org.springframework.util.StringUtils;

import java.lang.reflect.Field;
import java.util.*;


/**
 * 查询参数解析器
 *
 * @author whoimi
 * @since 2025-08-01
 **/
public class QueryParamParser {

    /**
     * 解析查询对象，生成查询条件映射
     */
    public static Map<String, QueryCondition> parseQueryParams(Object queryObj) {
        if (queryObj == null) {
            return Collections.emptyMap();
        }
        Map<String, QueryCondition> params = new HashMap<>();
        Class<?> clazz = queryObj.getClass();

        // 获取所有字段（包括父类字段）
        Field[] fields = getAllFields(clazz);

        for (Field field : fields) {
            field.setAccessible(true);
            SqlOperate sqlOperate = field.getAnnotation(SqlOperate.class);

            if (sqlOperate != null) {
                try {
                    Object value = field.get(queryObj);
                    if (value != null && shouldIncludeValue(value)) {
                        // 生成参数名：优先使用dbFieldName，其次使用alias.字段名，最后使用字段名
                        String paramName = generateParamName(field, sqlOperate);

                        // 根据操作符处理值
                        QueryCondition condition = new QueryCondition(paramName, sqlOperate.operate(), value);

                        params.put(paramName, condition);
                    }
                } catch (IllegalAccessException e) {
                    // 忽略无法访问的字段
                }
            }
        }

        return params;
    }

    /**
     * 生成参数名
     */
    private static String generateParamName(Field field, SqlOperate sqlOperate) {
        String paramName = sqlOperate.dbFieldName();
        if (!StringUtils.hasText(paramName)) {
            paramName = field.getName();
        }
        if (StringUtils.hasText(sqlOperate.alias()) && !paramName.contains(".")) {
            paramName = sqlOperate.alias() + "." + paramName;
        }
        return paramName;
    }

    /**
     * 判断值是否应该包含在查询条件中
     */
    private static boolean shouldIncludeValue(Object value) {
        if (value instanceof String) {
            return StringUtils.hasText((String) value);
        }
        if (value instanceof Collection) {
            return !((Collection<?>) value).isEmpty();
        }
        return true;
    }

    /**
     * 获取类的所有字段（包括父类）
     */
    private static Field[] getAllFields(Class<?> clazz) {
        List<Field> fields = new ArrayList<>();
        while (clazz != null) {
            fields.addAll(Arrays.asList(clazz.getDeclaredFields()));
            clazz = clazz.getSuperclass();
        }
        return fields.toArray(new Field[0]);
    }
}
